package com.redwine.app.utils;

import android.app.Activity;
import android.content.ComponentName;
import android.content.ContentUris;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.Bitmap.Config;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.media.ExifInterface;
import android.media.MediaScannerConnection;
import android.net.Uri;
import android.os.Build;
import android.os.Environment;
import android.provider.DocumentsContract;
import android.provider.MediaStore;
import android.util.Log;
import android.widget.Toast;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Locale;

import static android.R.attr.data;

public class ImageUtils {


    public static final int WECHAT_SHARE_BITMAP_SIZE = 32 * 1000;

    private static final String TAG = ImageUtils.class.getName();


    public static Bitmap getWeChatShareBitmap(Bitmap image) {
        if (image == null)
            return null;
        if (image.getByteCount() < WECHAT_SHARE_BITMAP_SIZE) {
            return image;
        } else {
            Bitmap bitmap = Bitmap.createBitmap(
                    image.getWidth(), image.getHeight(), Config.ARGB_8888);
            Paint paint = new Paint();
            Canvas canvas = new Canvas(bitmap);
            canvas.drawColor(0xFFFFFFFF);
            canvas.drawBitmap(image, 0, 0, paint);
            return Bitmap.createScaledBitmap(bitmap, 100, 100, false);
        }

    }

    public static final File PHOTO_DIR = new File(Environment.getExternalStorageDirectory()
            + "/DCIM/Camera");
    public static final int TAKE_OR_CHOOSE_PHOTO = 3024;
    public static File mCurrentPhotoFile;

    public static void takeOrChoosePhoto(Activity context, int requestCode) {
        PHOTO_DIR.mkdirs();
        mCurrentPhotoFile = new File(PHOTO_DIR, getPhotoFileName());
        Uri outputFileUri = Uri.fromFile(mCurrentPhotoFile);
        // Camera.
        final List<Intent> cameraIntents = new ArrayList<Intent>();
        final Intent captureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        final PackageManager packageManager = context.getPackageManager();
        final List<ResolveInfo> listCam = packageManager.queryIntentActivities(captureIntent, 0);
        for (ResolveInfo res : listCam) {
            final String packageName = res.activityInfo.packageName;
            final Intent intent = new Intent(captureIntent);
            intent.setComponent(new ComponentName(res.activityInfo.packageName,
                    res.activityInfo.name));
            intent.setPackage(packageName);
            intent.putExtra(MediaStore.EXTRA_OUTPUT, outputFileUri);
            cameraIntents.add(intent);
        }
        context.startActivityForResult(cameraIntents.get(0), requestCode);
    }


    public static String getPhotoFileName() {
        Date date = new Date(System.currentTimeMillis());
        SimpleDateFormat dateFormat = new SimpleDateFormat("'IMG'_yyyyMMdd_HHmmss", Locale.US);
        return dateFormat.format(date) + ".jpg";
    }


    public static File getPhotoFromResult(Context context, Intent data) {
        final boolean isCamera;
        if (data == null) {
            isCamera = true;
        } else {
            isCamera = MediaStore.ACTION_IMAGE_CAPTURE.equals(data.getAction());
        }
        File f = null;
        if (isCamera) {
            f = mCurrentPhotoFile;
        } else {
            if (data != null) {
                try {
                    String path = getRealPathFromURI(context, data.getData());
                    f = new File(path);
                    if ((f == null) || !f.exists()) {
                        Log.e(TAG, "Cannot load photo:" + path);
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                }
                if ((f == null) || !f.exists()) {
                    Log.e(TAG, "error loading file!");
                }
            }
        }
        return f;
    }

    public static String getPhotoFromResultStr(Context context, Boolean isCamera, Intent data) {
        if (isCamera) {
            return mCurrentPhotoFile.getAbsolutePath();
        } else {
            if (data != null) {
                try {
                    String path = getRealPathFromURI(context, data.getData());
                    return path;
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }
        return "";
    }


    private static String getRealPathFromURI(final Context context, final Uri uri) {

        final boolean isKitKat = Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT;
        // DocumentProvider
        if (isKitKat && DocumentsContract.isDocumentUri(context, uri)) {
            if (isExternalStorageDocument(uri)) {
                final String docId = DocumentsContract.getDocumentId(uri);
                final String[] split = docId.split(":");
                final String type = split[0];

                if ("primary".equalsIgnoreCase(type)) {
                    return Environment.getExternalStorageDirectory() + "/" + split[1];
                }

            }
            // DownloadsProvider
            else if (isDownloadsDocument(uri)) {

                final String id = DocumentsContract.getDocumentId(uri);
                final Uri contentUri = ContentUris.withAppendedId(
                        Uri.parse("content://downloads/public_downloads"), Long.valueOf(id));

                return getDataColumn(context, contentUri, null, null);
            }
            // MediaProvider
            else if (isMediaDocument(uri)) {
                final String docId = DocumentsContract.getDocumentId(uri);
                final String[] split = docId.split(":");
                final String type = split[0];

                Uri contentUri = null;
                if ("image".equals(type)) {
                    contentUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
                } else if ("video".equals(type)) {
                    contentUri = MediaStore.Video.Media.EXTERNAL_CONTENT_URI;
                } else if ("audio".equals(type)) {
                    contentUri = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;
                }

                final String selection = "_id=?";
                final String[] selectionArgs = {
                        split[1]
                };

                return getDataColumn(context, contentUri, selection, selectionArgs);
            }
        } else if (uri == null) {
            Cursor myCursor = null;
            try {
                String[] largeFileProjection = {
                        MediaStore.Images.ImageColumns._ID,
                        MediaStore.Images.ImageColumns.DATA};

                String largeFileSort = MediaStore.Images.ImageColumns._ID + " DESC";
                myCursor = context.getContentResolver().query(
                        MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
                        largeFileProjection, null, null, largeFileSort);
                String largeImagePath = "";

                if (myCursor.moveToFirst()) {
                    largeImagePath = myCursor.getString(1);
                    Uri imageCaptureUri = Uri.fromFile(new File(largeImagePath));
                    return imageCaptureUri.getPath();
                }
            } catch (Exception e) {
                e.printStackTrace();
            } finally {
                if (myCursor != null) {
                    myCursor.close();
                }
            }

        }
        // MediaStore (and general)
        else if ("content".equalsIgnoreCase(uri.getScheme())) {

            // Return the remote address
            return getDataColumn(context, uri, null, null);
        }
        // File
        else if ("file".equalsIgnoreCase(uri.getScheme())) {
            return uri.getPath();
        }

        return null;
    }


    public static boolean isExternalStorageDocument(Uri uri) {
        return "com.android.externalstorage.documents".equals(uri.getAuthority());
    }

    public static boolean isDownloadsDocument(Uri uri) {
        return "com.android.providers.downloads.documents".equals(uri.getAuthority());
    }

    public static boolean isMediaDocument(Uri uri) {
        return "com.android.providers.media.documents".equals(uri.getAuthority());
    }

    public static String getDataColumn(Context context, Uri uri, String selection,
                                       String[] selectionArgs) {

        Cursor cursor = null;
        final String column = "_data";
        final String[] projection = {
                column
        };

        try {
            cursor = context.getContentResolver().query(uri, projection, selection, selectionArgs,
                    null);
            if ((cursor != null) && cursor.moveToFirst()) {
                final int column_index = cursor.getColumnIndexOrThrow(column);
                return cursor.getString(column_index);
            }
        } finally {
            if (cursor != null) {
                cursor.close();
            }
        }
        return null;
    }

    public static final int PHOTO_PICKED_WITH_DATA = 3;

    public static void doCropAvatarPhoto(Activity context, File f) {
        if ((f == null) || !f.exists()) {
            Toast.makeText(context, "文件不存在，无法裁剪照片", Toast.LENGTH_LONG).show();
            return;
        }
        try {
            // Add the image to the media store
            MediaScanFile(context, f.getAbsolutePath());
            // Launch gallery to crop the photo
            final Intent intent = getCropAvatarImageIntent(Uri.fromFile(f), context);
            context.startActivityForResult(intent, PHOTO_PICKED_WITH_DATA);
        } catch (Exception e) {
            Log.e(TAG, "Cannot crop image", e);
            Toast.makeText(context, "无法裁剪照片", Toast.LENGTH_LONG).show();
        }
    }


    public static void MediaScanFile(Context context, String path) {
        MediaScannerConnection
                .scanFile(context, new String[]{path},
                        new String[]{null}, null);
        Intent mediaScanIntent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
        File f = new File(path);
        Uri contentUri = Uri.fromFile(f);
        mediaScanIntent.setData(contentUri);
        context.sendBroadcast(mediaScanIntent);
    }

    public static File mTempCropFile;

    public static Intent getCropAvatarImageIntent(Uri photoUri, Context context) {
        Intent intent = new Intent("com.android.camera.action.CROP");
        intent.setDataAndType(photoUri, "image/*");
        intent.putExtra("crop", "true");
        intent.putExtra("scale", true);
        intent.putExtra("scaleUpIfNeeded", true);
        intent.putExtra("aspectX", 1);
        intent.putExtra("aspectY", 1);
        intent.putExtra("outputX", 200);
        intent.putExtra("outputY", 200);
        intent.putExtra("return-data", false);
        if (mTempCropFile == null) {
            File dir = FileUtils.getCacheDir();
            if (dir == null) {
                return null;
            }
            dir.mkdirs();
            mTempCropFile = new File(dir, "temp_crop.jpg");
        }
        mTempCropFile.delete();
        intent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(mTempCropFile));
        return intent;
    }


    public static Bitmap getCroppedImage() {
        if ((mTempCropFile == null) || !mTempCropFile.exists()) {
            return null;
        }
        Bitmap bmp = BitmapFactory.decodeFile(mTempCropFile.getAbsolutePath());
        return bmp;

    }

    public static File getTempCropFile() {
        if ((mTempCropFile == null) || !mTempCropFile.exists()) {
            return null;
        }
        return mTempCropFile;
    }


    //把bitmap转化为二进制
    public static byte[] getBytesFromBitmap(Bitmap bitmap) {
        final ByteArrayOutputStream out = new ByteArrayOutputStream();
        try {
            //            bitmap.compress(Bitmap.CompressFormat.JPEG, 75, out);
            Bitmap bt = compressImage(suoxiao(bitmap));//先把宽高都缩小一半，在等质量压缩
            //            Bitmap bt = compressImage(bitmap);
            bt.compress(Bitmap.CompressFormat.PNG, 100, out);//多压缩
            out.flush();
            return out.toByteArray();
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            if (out != null) {
                try {
                    out.close();
                } catch (Exception e) {

                }
            }
        }
        return null;
    }

    //等质量压缩，可以设置图片不超过1M
    private static Bitmap compressImage(Bitmap image) {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        image.compress(Bitmap.CompressFormat.PNG, 100, baos);//质量压缩方法，这里100表示不压缩，把压缩后的数据存放到baos中
        int options = 100;
        while (baos.toByteArray().length / 1024 > 1000) {  //循环判断如果压缩后图片是否大于100kb,大于继续压缩
            baos.reset();//重置baos即清空baos
            image.compress(Bitmap.CompressFormat.JPEG, options, baos);//这里压缩options%，把压缩后的数据存放到baos中
            options -= 10;//每次都减少10
        }
        ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());//把压缩后的数据baos存放到ByteArrayInputStream中
        Bitmap bitmap = BitmapFactory.decodeStream(isBm, null, null);//把ByteArrayInputStream数据生成图片
        return bitmap;
    }


    //qcl图片比例缩小方法
    private static Bitmap suoxiao(Bitmap bm) {
        // 获得图片的宽高
        int width = bm.getWidth();
        int height = bm.getHeight();
        // 计算缩放比例
        float scaleWidth = 0.5f;
        float scaleHeight = 0.5f;
        // 取得想要缩放的matrix参数
        Matrix matrix = new Matrix();
        matrix.postScale(scaleWidth, scaleHeight);
        // 得到新的图片
        Bitmap newbm = Bitmap.createBitmap(bm, 0, 0, width, height, matrix, true);
        return newbm;
    }


    /**
     * 获取图片的旋转角度
     *
     * @param path 图片绝对路径
     * @return 图片的旋转角度
     */
    public static int getBitmapDegree(String path) {
        int degree = 0;
        try {
            // 从指定路径下读取图片，并获取其EXIF信息
            ExifInterface exifInterface = new ExifInterface(path);
            // 获取图片的旋转信息
            int orientation = exifInterface.getAttributeInt(ExifInterface.TAG_ORIENTATION, ExifInterface.ORIENTATION_NORMAL);
            switch (orientation) {
                case ExifInterface.ORIENTATION_ROTATE_90:
                    degree = 90;
                    break;
                case ExifInterface.ORIENTATION_ROTATE_180:
                    degree = 180;
                    break;
                case ExifInterface.ORIENTATION_ROTATE_270:
                    degree = 270;
                    break;
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        return degree;
    }

    /**
     * 将图片按照指定的角度进行旋转
     *
     * @param bitmap 需要旋转的图片
     * @param degree 指定的旋转角度
     * @return 旋转后的图片
     */
    public static Bitmap rotateBitmapByDegree(Bitmap bitmap, int degree) {
        // 根据旋转角度，生成旋转矩阵
        Matrix matrix = new Matrix();
        matrix.postRotate(degree);
        // 将原始图片按照旋转矩阵进行旋转，并得到新的图片
        Bitmap newBitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);
        if (bitmap != null & !bitmap.isRecycled()) {
            bitmap.recycle();
        }
        return newBitmap;
    }


}

